#pragma once
#ifndef SDK__MATERIAL__CODER__HH
#define SDK__MATERIAL__CODER__HH

#include <QtGui/QtGui>

class MaterialTextEdit;

class MaterialCoderLineArea : public QWidget
{
public:
	MaterialCoderLineArea(MaterialTextEdit *editor) ;
	~MaterialCoderLineArea();

	QSize sizeHint() const;

protected:
	void paintEvent(QPaintEvent *event);

private:
	MaterialTextEdit *mEditor;
};
class MaterialCodeHighlighter : public QSyntaxHighlighter
{
Q_OBJECT

public:
	MaterialCodeHighlighter(QTextDocument *parent = 0);

	struct Rule
	{
		Rule( ){}
		Rule( const QRegExp &_pattern, const QTextCharFormat& fmt ) : pattern(_pattern), format(fmt){}
		Rule( const Rule& rk ){ format = rk.format; pattern = rk.pattern; }
		Rule& operator=( const Rule& rk ){ format = rk.format; pattern = rk.pattern; return *this; }
		~Rule( ){}

		QRegExp pattern;
		QTextCharFormat format;
	};
	typedef QVector<Rule> RuleList;
	
	RuleList Rules;
	RuleList LangRules;
protected:
	void highlightBlock(const QString &text);

private:

	QRegExp commentStartExpression;
	QRegExp commentEndExpression;

	QTextCharFormat keywordFormat;
	QTextCharFormat classFormat;
	QTextCharFormat numberFormat;
	QTextCharFormat singleLineCommentFormat;
	QTextCharFormat multiLineCommentFormat;
	QTextCharFormat quotationFormat;
	QTextCharFormat functionFormat;
};
class MaterialCompleter : public QMenu
{
	Q_OBJECT
	QVBoxLayout*		mLay;
	QListWidget*		mList;
	QTextCursor			mCursor;
	MaterialTextEdit*	mEdit;
	QStringList			mWords;
public:
	MaterialCompleter( MaterialTextEdit * parent );
	~MaterialCompleter();
	
	void popup( const QPoint &pos );
protected slots:
	void insertCompletion( QListWidgetItem* itm );
};
class MaterialTextEdit : public QPlainTextEdit
{
	Q_OBJECT
		MaterialCodeHighlighter *	mHighlighter;
		MaterialCompleter*			mCompleter;
public:
	MaterialTextEdit( QTabWidget * parent );
	~MaterialTextEdit();
	
	void setupEditor( );
	void lineNumberAreaPaintEvent(QPaintEvent *event);
	int lineNumberAreaWidth();

	QString currentLine( int line_offset = 0 ) const;
	QString findIndentationLevel( int line_offset = 0, int level_offset = 0 ) const;
	QString textUnderCursor() const;

protected:
	void resizeEvent(QResizeEvent *event);
	void keyPressEvent( QKeyEvent *evt );

private slots:
	void updateLineNumberAreaWidth(int newBlockCount);
	void highlightCurrentLine();
	void updateLineNumberArea(const QRect &, int);

 private:
     MaterialCoderLineArea *mLineArea;
};

#endif